package com.ai.dmc.utils.export.excelhelper;

import java.io.IOException;
import java.io.OutputStream;
import java.io.UnsupportedEncodingException;
import java.util.Collection;
import java.util.List;

import javax.servlet.http.HttpServletResponse;

import org.apache.log4j.Logger;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;

public class SimpleTExcelExporter<T> implements ITExcelExporter<T>{
	private static final Logger logger = Logger.getLogger(SimpleTExcelExporter.class);
	private final String ioMsg="IO exception occurred when downloading xls data";
	private final String closeMsg="Close output stream failed";
	private final String encodingMsg="Encoding in header not supported";
	
	private TExcelFactory<T> tExcelFactory;
	
	public TExcelFactory<T> getTExcelFactory() {
		return tExcelFactory;
	}

	public void setTExcelFactory(TExcelFactory<T> excelFactory) {
		tExcelFactory = excelFactory;
	}
	
	/**
	 * 以类对象的方式组织数据的导出方法,该方法导出单行表头的Excel
	 * 通过设置返回客户端类型的方式，来直接将excel表格内容送到客户端保存
	 * @param sheetName：表单的标签名称,当为null或者空字符串时，将使用defaultSheetName
	 * @param headers: 表单的表头，不能为null
	 * @param dataset：表单的数据（以类对象的方式组织）
	 * @param methodNames：获取类对象属性值的方法，可以为null，当为null时，将按照类对象中属性的顺序来获取相应的值
	 * 					   并且，类对象属性值的获取方法必须以get或者is开头，且遵循hibernate定义bean的规则
	 * @param response
	 * @throws Exception
	 */
	public void exportExcelByObj(String sheetName, String[] headers,
			Collection<T> dataset, String[] methodNames, String pattern, HttpServletResponse response){
		response.reset();
		response.setContentType("application/vnd.ms-excel; charset=GBK");
		OutputStream os = null;
		try {
		    response.addHeader("content-disposition", "attachment;filename=\""
	                + java.net.URLEncoder.encode(sheetName + ".xls", "UTF-8")
	                + "\"");
			os = response.getOutputStream();
			if(tExcelFactory == null){
				tExcelFactory = new TExcelFactory<T>();
			}
			HSSFWorkbook workbook = tExcelFactory.createWorkbookByObj(sheetName, headers, dataset, methodNames, pattern);
			workbook.write(os);
		}catch (UnsupportedEncodingException uee) {
            logger.error(encodingMsg);
            logger.debug("SimpleExcelExporter.exportExcelByL():",uee);
        } 
		catch (IOException ie) {
			logger.error(ioMsg);
			logger.debug("SimpleTExcelExporter.exportExcelByObj():",ie);
		}finally{
			try {
				os.flush();
				os.close();
			} catch (IOException ie) {
				logger.error(closeMsg);
				logger.debug("SimpleTExcelExporter.exportExcelByObj():",ie);
			}
		}
	}

	/**
	 * 以类对象的方式组织数据的导出方法,该方法导出多行表头的Excel
	 * 通过设置返回客户端类型的方式，来直接将excel表格内容送到客户端保存
	 * @param sheetName：表单的标签名称,当为null或者空字符串时，将使用defaultSheetName
	 * @param headerList: 表单的表头，不能为null，必须遵循CellBean的规则
	 * @param dataset：表单的数据（以类对象的方式组织）
	 * @param methodNames：获取类对象属性值的方法，可以为null，当为null时，将按照类对象中属性的顺序来获取相应的值
	 * 					   并且，类对象属性值的获取方法必须以get或者is开头，且遵循hibernate定义bean的规则
	 * @param response
	 * @throws Exception
	 */
	public void exportExcelByObj(String sheetName, List<CellBean> headerList,
			Collection<T> dataset, String[] methodNames, String pattern,
			HttpServletResponse response) {
		response.reset();
		response.setContentType("application/vnd.ms-excel; charset=GBK");
		OutputStream os = null;
		try {
		   response.addHeader("content-disposition", "attachment;filename=\""
                    + java.net.URLEncoder.encode(sheetName + ".xls", "UTF-8")
                    + "\"");
			os = response.getOutputStream();
			if(tExcelFactory == null){
				tExcelFactory = new TExcelFactory<T>();
			}
			HSSFWorkbook workbook = tExcelFactory.createWorkbookByObj(sheetName, headerList, dataset, methodNames, pattern);
			workbook.write(os);
		} catch (IOException ie) {
			logger.error(ioMsg);
			logger.debug("SimpleTExcelExporter.exportExcelByObj():",ie);
		}finally{
			try {
				os.flush();
				os.close();
			} catch (IOException ie) {
				logger.error(closeMsg);
				logger.debug("SimpleTExcelExporter.exportExcelByObj():",ie);
			}
		}
		
	}
}
